'use strict';

Object.defineProperty(exports, '__esModule', { value: true });

function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; }

var crypto = _interopDefault(require('crypto'));

function createCommonjsModule(fn, module) {
	return module = { exports: {} }, fn(module, module.exports), module.exports;
}

var jwt_1 = createCommonjsModule(function (module) {
/*
 * jwt-simple
 *
 * JSON Web Token encode and decode module for node.js
 *
 * Copyright(c) 2011 Kazuhito Hokamura
 * MIT Licensed
 */

/**
 * module dependencies
 */



/**
 * support algorithm mapping
 */
var algorithmMap = {
  HS256: 'sha256',
  HS384: 'sha384',
  HS512: 'sha512',
  RS256: 'RSA-SHA256'
};

/**
 * Map algorithm to hmac or sign type, to determine which crypto function to use
 */
var typeMap = {
  HS256: 'hmac',
  HS384: 'hmac',
  HS512: 'hmac',
  RS256: 'sign'
};


/**
 * expose object
 */
var jwt = module.exports;


/**
 * version
 */
jwt.version = '0.5.6';

/**
 * Decode jwt
 *
 * @param {Object} token
 * @param {String} key
 * @param {Boolean} [noVerify]
 * @param {String} [algorithm]
 * @return {Object} payload
 * @api public
 */
jwt.decode = function jwt_decode(token, key, noVerify, algorithm) {
  // check token
  if (!token) {
    throw new Error('No token supplied');
  }
  // check segments
  var segments = token.split('.');
  if (segments.length !== 3) {
    throw new Error('Not enough or too many segments');
  }

  // All segment should be base64
  var headerSeg = segments[0];
  var payloadSeg = segments[1];
  var signatureSeg = segments[2];

  // base64 decode and parse JSON
  var header = JSON.parse(base64urlDecode(headerSeg));
  var payload = JSON.parse(base64urlDecode(payloadSeg));

  if (!noVerify) {
    if (!algorithm && /BEGIN( RSA)? PUBLIC KEY/.test(key.toString())) {
      algorithm = 'RS256';
    }

    var signingMethod = algorithmMap[algorithm || header.alg];
    var signingType = typeMap[algorithm || header.alg];
    if (!signingMethod || !signingType) {
      throw new Error('Algorithm not supported');
    }

    // verify signature. `sign` will return base64 string.
    var signingInput = [headerSeg, payloadSeg].join('.');
    if (!verify(signingInput, key, signingMethod, signingType, signatureSeg)) {
      throw new Error('Signature verification failed');
    }

    // Support for nbf and exp claims.
    // According to the RFC, they should be in seconds.
    if (payload.nbf && Date.now() < payload.nbf*1000) {
      throw new Error('Token not yet active');
    }

    if (payload.exp && Date.now() > payload.exp*1000) {
      throw new Error('Token expired');
    }
  }

  return payload;
};


/**
 * Encode jwt
 *
 * @param {Object} payload
 * @param {String} key
 * @param {String} algorithm
 * @param {Object} options
 * @return {String} token
 * @api public
 */
jwt.encode = function jwt_encode(payload, key, algorithm, options) {
  // Check key
  if (!key) {
    throw new Error('Require key');
  }

  // Check algorithm, default is HS256
  if (!algorithm) {
    algorithm = 'HS256';
  }

  var signingMethod = algorithmMap[algorithm];
  var signingType = typeMap[algorithm];
  if (!signingMethod || !signingType) {
    throw new Error('Algorithm not supported');
  }

  // header, typ is fixed value.
  var header = { typ: 'JWT', alg: algorithm };
  if (options && options.header) {
    assignProperties(header, options.header);
  }

  // create segments, all segments should be base64 string
  var segments = [];
  segments.push(base64urlEncode(JSON.stringify(header)));
  segments.push(base64urlEncode(JSON.stringify(payload)));
  segments.push(sign(segments.join('.'), key, signingMethod, signingType));

  return segments.join('.');
};

/**
 * private util functions
 */

function assignProperties(dest, source) {
  for (var attr in source) {
    if (source.hasOwnProperty(attr)) {
      dest[attr] = source[attr];
    }
  }
}

function verify(input, key, method, type, signature) {
  if(type === "hmac") {
    return (signature === sign(input, key, method, type));
  }
  else if(type == "sign") {
    return crypto.createVerify(method)
                 .update(input)
                 .verify(key, base64urlUnescape(signature), 'base64');
  }
  else {
    throw new Error('Algorithm type not recognized');
  }
}

function sign(input, key, method, type) {
  var base64str;
  if(type === "hmac") {
    base64str = crypto.createHmac(method, key).update(input).digest('base64');
  }
  else if(type == "sign") {
    base64str = crypto.createSign(method).update(input).sign(key, 'base64');
  }
  else {
    throw new Error('Algorithm type not recognized');
  }

  return base64urlEscape(base64str);
}

function base64urlDecode(str) {
  return Buffer.from(base64urlUnescape(str), 'base64').toString();
}

function base64urlUnescape(str) {
  str += new Array(5 - str.length % 4).join('=');
  return str.replace(/\-/g, '+').replace(/_/g, '/');
}

function base64urlEncode(str) {
  return base64urlEscape(Buffer.from(str).toString('base64'));
}

function base64urlEscape(str) {
  return str.replace(/\+/g, '-').replace(/\//g, '_').replace(/=/g, '');
}
});

const db = uniCloud.database();
const collection1 = db.collection('ha_report_list');
const collection2 = db.collection('ha_report_record');
const collection3 = db.collection('ha_group_person');

async function checkReportRecord(report_id,gp_id) {
	let res1 = await collection1
		.doc(report_id)
		.get();

	if (res1.data && res1.affectedDocs === 1) ; else {
		return false
	}

	let res2 = await collection2
		.where({
			report_id,
			gp_id
		})
		.orderBy("create_time", "desc")
		.limit(1)
		.get();

	if (res2.data && res2.affectedDocs >= 1) {
		if (res2.data[0].allow_modify === 1) {
			return true;
		}

		// 检查间隔时间 TODO
		// res1.data[0].interval_hour

		return false;
	}

	return true;
}

async function getOneRecord(record_id) {
	let res2 = await collection2
		.doc(record_id)
		.get();

	if (res2.data && res2.affectedDocs === 1) ; else {
		return false;
	}

	if (res2.data[0].hasOwnProperty('report_id') == false) {
		return false;
	}

	let res1 = await collection1
		.doc(res2.data[0].report_id)
		.get();

	if (res1.data && res1.affectedDocs === 1) ; else {
		return false;
	}

	return {
		schema: res1.data[0].content,
		model: res2.data[0].model
	}
}

async function getReportRecord(report_id,condition = {}) {
	let res2 = await collection2
		.where(
			Object.assign({
				report_id
			},condition)
		)
		.orderBy("create_time", "asc")
		.get();

	if (res2.data && res2.affectedDocs >= 1) ; else {
		return false;
	}

	let recordList = [];
	for (var i = 0; i < res2.data.length; i++) {
		let res3 = await collection3
			.doc(
				res2.data[i].gp_id
			)
			.get();

		recordList.push(
			Object.assign({
				person_name: res3.data[0].person_name,
				person_identity: res3.data[0].person_identity
			},
			res2.data[i].model
			)
		);
	}

	return recordList;
}

var reportFunc = {
	checkReportRecord,
	getOneRecord,
	getReportRecord
};

const db$1 = uniCloud.database();

async function Perform(event) {
	if (!event.report_id) {
		return {
			status: -1,
			msg: '出错了'
		}
	}

	if (!event.gp_id) {
		return {
			status: -1,
			msg: '出错了'
		}
	}

	let isPass = await reportFunc.checkReportRecord(event.report_id,event.gp_id);

	if (isPass != true) {
		return {
			status: -2,
			msg: '请不要重复提交！'
		}
	}

	let data = {
		report_id: event.report_id,
		gp_id: event.gp_id,
		create_time: Date.now(),
		allow_modify: 0,
		model: event.model
	};

	const collection = db$1.collection('ha_report_record');
	await collection.add(data);

	return {
		status: 0,
		msg: '提交成功！'
	}
}

exports.main = Perform;
